package com.sinux.generality.provider.pay.util;


import com.sinux.generality.provider.pay.config.WeChatPayConfigure;

import com.wechat.pay.contrib.apache.httpclient.WechatPayHttpClientBuilder;
import com.wechat.pay.contrib.apache.httpclient.auth.AutoUpdateCertificatesVerifier;
import com.wechat.pay.contrib.apache.httpclient.auth.PrivateKeySigner;
import com.wechat.pay.contrib.apache.httpclient.auth.WechatPay2Credentials;
import com.wechat.pay.contrib.apache.httpclient.auth.WechatPay2Validator;
import com.wechat.pay.contrib.apache.httpclient.util.PemUtil;
import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.ParseException;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.util.EntityUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.IOException;
import java.io.InputStream;
import java.security.PrivateKey;
import java.security.cert.X509Certificate;
import java.util.HashMap;
import java.util.Map;

/****
 * @className WxchatHttpUtil
 * @describe 请求微信支付工具类
 * @author lhz
 * @date  2021/10/25 04:03
 * @version 0.0.1
 */

public class WxChatHttpUtil {
    public static Map<String, X509Certificate> certSet = new HashMap<>();
    private static CloseableHttpClient httpClient;
    public  static PrivateKey merchantPrivateKey;
    private static volatile boolean isInitialize;
    private final static Logger logger = LoggerFactory.getLogger("WxchatHttpUtil.class");

    static {
        initialization();
    }

    private static void initialization() {
        if (!isInitialize) {
            try {
                InputStream resourceAsStream = WxChatHttpUtil.class.getClassLoader().getResourceAsStream(WeChatPayConfigure.PRIVATE_KEY);
                // 加载商户私钥（privateKey：私钥字符串）
                merchantPrivateKey = PemUtil
                        .loadPrivateKey(resourceAsStream);
                // 加载平台证书（mchId：商户号,mchSerialNo：商户证书序列号,apiV3Key：V3密钥）
                AutoUpdateCertificatesVerifier verifier = new AutoUpdateCertificatesVerifier(
                        new WechatPay2Credentials(WeChatPayConfigure.merchantId, new PrivateKeySigner(WeChatPayConfigure.serialNo,
                                merchantPrivateKey)), WeChatPayConfigure.apiV3key.getBytes("utf-8"));
                // 初始化httpClient
                httpClient = WechatPayHttpClientBuilder.create()
                        .withMerchant(WeChatPayConfigure.merchantId, WeChatPayConfigure.serialNo, merchantPrivateKey)
                        .withValidator(new WechatPay2Validator(verifier)).build();
                isInitialize = true;
            } catch (Exception e) {
                logger.error("微信请求工具类初始化异常:{}", e.getMessage(), e);
            }
        }
    }

    /**
     * post提交json数据
     *
     * @param url
     * @param jsonStr
     * @return
     */
    public static Map doPostJson(String url, String jsonStr) {
        HttpPost httpPost = new HttpPost(url);
        Map<String, Object> map = new HashMap<>(4);
        try {
            httpPost.addHeader("Accept", "application/json");
            httpPost.addHeader("Content-type", "application/json; charset=utf-8");
            RequestConfig requestConfig = RequestConfig.custom().setSocketTimeout(10000).setConnectTimeout(10000).build();
            httpPost.setConfig(requestConfig);
            StringEntity myEntity = new StringEntity(jsonStr, "UTF-8");
            httpPost.setEntity(myEntity);
            HttpResponse response = httpClient.execute(httpPost);
            HttpEntity resEntity = response.getEntity();
            int statusCode = response.getStatusLine().getStatusCode();
            map.put("code", statusCode);
            if (resEntity != null) {
                try {
                    String respBody = EntityUtils.toString(resEntity, "UTF-8");
                    map.put("result", respBody);
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            httpPost.releaseConnection();
        }
        return map;
    }


    /**
     * 发送 get请求
     *
     * @return
     */
    public static Map get(String url) {
        String result = null;
        // 创建httpget.
        HttpGet httpget = new HttpGet(url);
        Map<String, Object> map = new HashMap<>(4);
        try {
            httpget.addHeader("Accept", "application/json");
            //设置请求和传输超时时间
            RequestConfig requestConfig = RequestConfig.custom().setSocketTimeout(50000).setConnectTimeout(50000).build();
            httpget.setConfig(requestConfig);
            // 执行get请求.
            CloseableHttpResponse response = httpClient.execute(httpget);
            try {
                // 获取响应实体
                HttpEntity resEntity = response.getEntity();
                int statusCode = response.getStatusLine().getStatusCode();
                map.put("code", statusCode);
                if (resEntity != null) {
                    try {
                        String respBody = EntityUtils.toString(resEntity, "UTF-8");
                        map.put("result", respBody);
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }
            } finally {
                response.close();
            }
        } catch (ClientProtocolException e) {
            e.printStackTrace();
        } catch (ParseException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }  finally {
            httpget.releaseConnection();
        }
        return map;
    }

}

